/**
 * 29/nov/2011 - fabio.melillo@gmail.com
 */
package org.unisannio.remote;

import it.unipr.ce.dsg.s2p.org.json.JSONObject;
import it.unipr.ce.dsg.s2p.peer.Peer;
import it.unipr.ce.dsg.s2p.sip.Address;

import org.unisannio.util.Converter;
import org.unisannio.util.ServiceInfo;

/**
 * Abstract class that implements only a simple dispatcher
 * for the different kinds of message that the SuperPeer can receive. 
 * 
 * @author Fabio Melillo
 *
 */
public abstract class SuperPeer extends Peer {
	

	protected Address sender;

	public SuperPeer(String pathConfig, String key, String peerName,int peerPort) {
		super(pathConfig, key, peerName, peerPort);
	}
	
	/**
	 * dispatches the different kind of messages arrived
	 * PUBLISH
	 * RETRACT_FROM_SERVICE
	 * RETRACT_FROM_ALL
	 * RECONNECT
	 * SUBSCRIBE
	 * UNSUBSCRIBE_FROM_SERVICE
	 * UNSUBSCRIBE_FROM_ALL
	 */
	@Override
	protected void onReceivedJSONMsg(JSONObject jsonMsg, Address sender) {
		try {
			System.out.println("JSON Received: "+jsonMsg);
			System.out.println("Sender: "+sender.toString());
			Converter converter=new Converter();
			this.sender=sender;
			int msgType = Integer.parseInt((String) jsonMsg.get("type"));
			ServiceInfo sinfo=(ServiceInfo) converter.unmarshal(jsonMsg);
			switch (msgType) {
			case Converter.PUBLISH:
				this.publish(sinfo);
				break;
			case Converter.RETRACT_FROM_SERVICE:
				this.retractFromService(sinfo);
				break;
			case Converter.RETRACT_FROM_ALL:
				this.retractFromAll(sinfo);
				break;
			case Converter.RECONNECT:
				this.reconnect(sinfo);
				break;
			case Converter.SUBSCRIBE:
				this.subscribe(sinfo);
				break;
			case Converter.UNSUBSCRIBE_FROM_ALL:
				this.unsubscribeFromAll(sinfo);
				break;
			case Converter.UNSUBSCRIBE_FROM_SERVICE:
				this.unsubscribeFromService(sinfo);
				break;
			default:
				break;
			}
			
			
		} catch (Exception e) {
			e.printStackTrace();
		}
		
		
	}
	
	
	protected abstract void unsubscribeFromAll(ServiceInfo sinfo);
	protected abstract void unsubscribeFromService(ServiceInfo sinfo);
	protected abstract void subscribe(ServiceInfo sinfo);
	protected abstract boolean reconnect(ServiceInfo sinfo);
	protected abstract void retractFromAll(ServiceInfo sinfo);
	protected abstract void retractFromService(ServiceInfo sinfo);
	protected abstract void publish(ServiceInfo sinfo);
	
	public Address getAddress(){
		return super.getAddress();
	}

}
